home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus 2000 #5 / Amiga Plus CD - 2000 - No. 5.iso / Tools / Dev / lame_src / i386 / choose_table.nas next >
Text File  |  2000-01-01  |  6KB  |  352 lines

  1. ; new count bit routine
  2. ;    part of this code is origined from
  3. ;    new GOGO-no-coda (1999, 2000)
  4. ;    Copyright (C) 1999 shigeo
  5. ;    modified by Keiichi SAKAI
  6.  
  7. %include "nasm.h"
  8.  
  9.     globaldef    choose_table_MMX
  10.     globaldef    MMX_masking
  11.  
  12.     externdef    largetbl
  13.     externdef    t1l
  14.     externdef    table23
  15.     externdef    table56
  16.     externdef    tableABC
  17.     externdef    tableDEF
  18.     externdef    linbits32
  19.     externdef    choose_table_H
  20.  
  21.     segment_data
  22.     align    16
  23. D14_14_14_14    dd    0x000E000E, 0x000E000E
  24. D15_15_15_15    dd    0xfff0fff0, 0xfff0fff0
  25. mul_add        dd    0x00010010, 0x00010010
  26. mul_add23    dd    0x00010003, 0x00010003
  27. mul_add56    dd    0x00010004, 0x00010004
  28.  
  29. choose_jump_table_L:
  30.     dd    table_MMX.L_case_0
  31.     dd    table_MMX.L_case_1
  32.     dd    table_MMX.L_case_2
  33.     dd    table_MMX.L_case_3
  34.     dd    table_MMX.L_case_45
  35.     dd    table_MMX.L_case_45
  36.     dd    table_MMX.L_case_67
  37.     dd    table_MMX.L_case_67
  38.     dd    table_MMX.L_case_8_15
  39.     dd    table_MMX.L_case_8_15
  40.     dd    table_MMX.L_case_8_15
  41.     dd    table_MMX.L_case_8_15
  42.     dd    table_MMX.L_case_8_15
  43.     dd    table_MMX.L_case_8_15
  44.     dd    table_MMX.L_case_8_15
  45.     dd    table_MMX.L_case_8_15
  46.  
  47.     segment_code
  48. ;
  49. ; use MMX
  50. ;
  51.  
  52.     align    16
  53. ; int choose_table(int *ix, int *end, int *s)
  54. choose_table_MMX:
  55.     mov    ecx,[esp+4]    ;ecx = begin
  56.     mov    edx,[esp+8]    ;edx = end
  57.     xor    eax,eax
  58.     sub    ecx,edx        ;ecx = begin-end(should be minus)
  59.      pxor    mm0,mm0        ;mm0=[0:0]
  60.     pxor    mm1,mm1        ;mm1=[0:0]
  61.     test    ecx,8
  62.     jz    .lp
  63.  
  64.     movq    mm1,[edx+ecx]
  65.     add    ecx,8
  66.     jz    .exit
  67.  
  68.     align    4
  69. .lp:
  70.     movq    mm4,[edx+ecx]
  71.     movq    mm5,[edx+ecx+8]
  72.     add    ecx,16
  73.     psubusw    mm4,mm0    ; $BK\Ev$O(B dword $B$G$J$$$H$$$1$J$$$N$@$,(B
  74.     psubusw    mm5,mm1    ; $B$=$s$J%3%^%s%I$O$J$$(B :-p
  75.     paddw    mm0,mm4 ; $B$,(B, $B$3$3$G07$&CM$NHO0O$O(B 8191+15 $B0J2<$J$N$GLdBj$J$$(B
  76.     paddw    mm1,mm5
  77.     jnz    .lp
  78. .exit:
  79.     psubusw    mm1,mm0    ; $B$3$l$bK\Ev$O(B dword $B$G$J$$$H$$$1$J$$(B
  80.     paddw    mm0,mm1
  81.  
  82.     movq    mm4,mm0
  83.     punpckhdq    mm4,mm4
  84.     psubusw    mm4,mm0    ; $B$3$l$bK\Ev$O(B dword $B$G$J$$$H$$$1$J$$(B
  85.     paddw    mm0,mm4
  86.     movd    eax,mm0
  87.  
  88.     cmp    eax,15
  89.     ja    .with_ESC
  90.     jmp    [choose_jump_table_L+eax*4]
  91.  
  92. .with_ESC1:
  93.     emms
  94.     mov    ecx, [esp+12]    ; *s
  95.     mov    [ecx], eax
  96.     or    eax,-1
  97.     ret
  98.  
  99. .with_ESC:
  100.     cmp    eax, 8191+15
  101.     ja    .with_ESC1
  102.  
  103.     sub    eax,15
  104.     push    ebx
  105.     push    esi
  106.     bsr    eax, eax
  107. %assign _P 4*2
  108.     movq    mm5, [D15_15_15_15]
  109.     movq    mm6, [D14_14_14_14]
  110.     movq    mm3, [mul_add]
  111.  
  112.     mov    ecx, [esp+_P+4]        ; = ix
  113. ;    mov    edx, [esp+_P+8]        ; = end
  114.     sub    ecx, edx
  115.  
  116.     xor    esi, esi    ; sum = 0
  117.     pxor    mm7, mm7    ; linbits_sum, 14$B$r1[$($?$b$N$N?t(B
  118.     test    ecx, 8
  119.     jz    .H_dual_lp1
  120.  
  121.     movq    mm0, [edx+ecx]
  122.     packssdw    mm0,mm7
  123.     movq    mm2, mm0
  124.     paddusw    mm0, mm5    ; mm0 = min(ix, 15)+0xfff0
  125.     pcmpgtw    mm2, mm6    ; 14$B$h$jBg$-$$$+!)(B
  126.     psubw    mm7, mm2    ; 14$B$h$jBg$-$$$H$-(B linbits_sum++;
  127.     pmaddwd    mm0, mm3    ; {0, 0, y, x}*{1, 16, 1, 16}
  128.     movd    ebx, mm0
  129.     mov    esi, [largetbl+ebx*4+(16*16+16)*4]
  130.     add    ecx,8
  131.  
  132.     jz    .H_dual_exit
  133.  
  134.     align   4
  135. .H_dual_lp1:
  136.     movq    mm0, [edx+ecx]
  137.     movq    mm1, [edx+ecx+8]
  138.     packssdw    mm0,mm1
  139.     movq    mm2, mm0
  140.     paddusw    mm0, mm5    ; mm0 = min(ix, 15)+0xfff0
  141.     pcmpgtw    mm2, mm6    ; 14$B$h$jBg$-$$$+!)(B
  142.     pmaddwd    mm0, mm3    ; {y, x, y, x}*{1, 16, 1, 16}
  143.     movd    ebx, mm0
  144.     punpckhdq    mm0,mm0
  145.     add    esi, [largetbl+ebx*4+(16*16+16)*4]
  146.     movd    ebx, mm0
  147.     add    esi, [largetbl+ebx*4+(16*16+16)*4]
  148.     add    ecx, 16
  149.     psubw    mm7, mm2    ; 14$B$h$jBg$-$$$H$-(B linbits_sum++;
  150.     jnz    .H_dual_lp1
  151.  
  152. .H_dual_exit:
  153.     pmov    mm1,mm7
  154.     punpckhdq    mm7,mm7
  155.     paddd    mm7,mm1
  156.     punpckldq    mm7,mm7
  157.  
  158.     pmaddwd    mm7, [linbits32+eax*8]    ; linbits
  159.     mov    ax, [choose_table_H+eax*2]
  160.  
  161.     movd    ecx, mm7
  162.     punpckhdq    mm7,mm7
  163.     movd    edx,mm7
  164.     emms
  165.     shl    edx, 16
  166.     add    ecx, edx
  167.  
  168.     add    ecx, esi
  169.  
  170.     pop    esi
  171.     pop    ebx
  172.  
  173.     mov    edx, ecx
  174.     and    ecx, 0xffff    ; ecx = sum2
  175.     shr    edx, 16    ; edx = sum
  176.  
  177.     cmp    edx, ecx
  178.     jle    .chooseE_s1
  179.     mov    edx, ecx
  180.     shr    eax, 8
  181. .chooseE_s1:
  182.     mov    ecx, [esp+12] ; *s
  183.     and    eax, 0xff
  184.     add    [ecx], edx
  185.     ret
  186.  
  187. table_MMX.L_case_0:
  188.     emms
  189.     ret
  190.  
  191. table_MMX.L_case_1:
  192.     emms
  193.     mov    eax, [esp+12] ; *s
  194.     mov    ecx, [esp+4] ; *ix
  195.     sub    ecx, edx
  196.     push    ebx
  197. .lp:
  198.     mov    ebx, [edx+ecx]
  199.     add    ebx, ebx
  200.     add    ebx, [edx+ecx+4]
  201.     movzx    ebx, byte [ebx+t1l]
  202.     add    [eax], ebx
  203.     add    ecx, 8
  204.     jnz    .lp
  205.     pop    ebx
  206.     mov    eax, 1
  207.     ret
  208.  
  209. table_MMX.L_case_45:
  210.     push    dword 7
  211.     mov    ecx, tableABC+9*8
  212.     jmp    from3
  213.  
  214. table_MMX.L_case_67:
  215.     push    dword 10
  216.     mov    ecx, tableABC
  217.     jmp    from3
  218.  
  219. table_MMX.L_case_8_15:
  220.     push    dword 13
  221.     mov    ecx, tableDEF
  222. from3:
  223.     mov    eax,[esp+8]    ;eax = *begin
  224. ;    mov    edx,[esp+12]    ;edx = *end
  225.  
  226.     push    ebx
  227.     sub    eax, edx
  228.  
  229.     movq    mm5,[mul_add]
  230.     pxor    mm2,mm2    ;mm2 = sum
  231.  
  232.     test    eax, 8
  233.     jz    .choose3_lp1
  234. ; odd length
  235.     movq    mm0,[edx+eax]    ;mm0 = ix[0] | ix[1]
  236.     packssdw    mm0,mm2
  237.  
  238.     pmaddwd    mm0,mm5
  239.     movd    ebx,mm0
  240.  
  241.     movq    mm2,  [ecx+ebx*8]
  242.  
  243.     add    eax,8
  244.     jz    .choose3_exit
  245.  
  246.     align    4
  247. .choose3_lp1
  248.     movq    mm0,[edx+eax]
  249.     movq    mm1,[edx+eax+8]
  250.     packssdw    mm0,mm1 ;mm0 = ix[0]|ix[1]|ix[2]|ix[3]
  251.     pmaddwd    mm0,mm5
  252.     movd    ebx,mm0
  253.     punpckhdq    mm0,mm0
  254.     paddd    mm2, [ecx+ebx*8]
  255.     movd    ebx,mm0
  256.     add    eax,16
  257.     paddd    mm2, [ecx+ebx*8]
  258.     jnz    .choose3_lp1
  259. .choose3_exit
  260. ;    xor    eax,eax
  261.     movd    ebx, mm2
  262.     punpckhdq    mm2,mm2
  263.     mov    ecx, ebx
  264.     and    ecx, 0xffff    ; ecx = sum2
  265.     shr    ebx, 16    ; ebx = sum1
  266.     movd    edx, mm2    ; edx = sum
  267.  
  268.     cmp    edx, ebx
  269.     jle    .choose3_s1
  270.     mov    edx, ebx
  271.     inc    eax
  272. .choose3_s1:
  273.     emms
  274.     pop    ebx
  275.     cmp    edx, ecx
  276.     jle    .choose3_s2
  277.     mov    edx, ecx
  278.     mov    eax, 2
  279. .choose3_s2:
  280.     pop    ecx
  281.     add    eax, ecx
  282.     mov    ecx, [esp+12] ; *s
  283.     add    [ecx], edx
  284.     ret
  285.  
  286. table_MMX.L_case_2:
  287.     push    dword 2
  288.     mov    ecx,table23
  289.     pmov    mm5,[mul_add23]
  290.     jmp    from2
  291. table_MMX.L_case_3:
  292.     push    dword 5
  293.     mov    ecx,table56
  294.     pmov    mm5,[mul_add56]
  295. from2:
  296.     mov    eax,[esp+8]    ;eax = *begin
  297. ;    mov    edx,[esp+12]    ;edx = *end
  298.     push    ebx
  299.     push    edi
  300.  
  301.     sub    eax, edx
  302.     xor    edi, edi
  303.     test    eax, 8
  304.     jz    .choose2_lp1
  305. ; odd length
  306.     movq    mm0,[edx+eax]    ;mm0 = ix[0] | ix[1]
  307.     pxor    mm2,mm2        ;mm2 = sum
  308.     packssdw    mm0,mm2
  309.  
  310.     pmaddwd    mm0,mm5
  311.     movd    ebx,mm0
  312.  
  313.     mov    edi,  [ecx+ebx*4]
  314.  
  315.     add    eax,8
  316.     jz    .choose2_exit
  317.  
  318.     align    4
  319. .choose2_lp1
  320.     movq    mm0,[edx+eax]
  321.     movq    mm1,[edx+eax+8]
  322.     packssdw    mm0,mm1 ;mm0 = ix[0]|ix[1]|ix[2]|ix[3]
  323.     pmaddwd    mm0,mm5
  324.     movd    ebx,mm0
  325.     punpckhdq    mm0,mm0
  326.     add    edi, [ecx+ebx*4]
  327.     movd    ebx, mm0
  328.     add    edi, [ecx+ebx*4]
  329.     add    eax,16
  330.     jnc    .choose2_lp1
  331. .choose2_exit
  332.     mov    ecx, edi
  333.     pop    edi
  334.     pop    ebx
  335.     pop    eax ; table num.
  336.     emms
  337.  
  338.     mov    edx, ecx
  339.     and    ecx, 0xffff    ; ecx = sum2
  340.     shr    edx, 16    ; edx = sum1
  341.  
  342.     cmp    edx, ecx
  343.     jle    .choose2_s1
  344.     mov    edx, ecx
  345.     inc    eax
  346. .choose2_s1:
  347.     mov    ecx, [esp+12] ; *s
  348.     add    [ecx], edx
  349.     ret
  350.  
  351.     end
  352.